<template>
    <div class="login-bg">
        <div class="login-box">
            <div class="login-top">
                <el-image :src="logo" fit="cover" alt="logo"></el-image>
            </div>
            <div class="login-center">
                <el-form :model="data.ruleForm" :rules="data.rules" ref="ruleFormRef">
                    <el-form-item prop="userName">
                      <!--oninput="value=value.replace(/[^\d]/g,'')"-->
                        <el-input
                            v-model.trim="data.ruleForm.userName"
                            size="large"
                            :prefix-icon="User"
                            maxlength="11"
                            placeholder="登录账号"
                            clearable
                        >
                        </el-input>
                    </el-form-item>
                    <el-form-item prop="password">
                        <el-input
                            v-model.trim="data.ruleForm.password"
                            :prefix-icon="Lock"
                            placeholder="用户密码"
                            @keyup.enter.native="submitForm(ruleFormRef)"
                            clearable
                            size="large"
                            show-password
                        >
                        </el-input>
                    </el-form-item>
                    <el-form-item prop="num">
                      <div style="display: flex; justify-content: space-between; width: 100%; align-items: end;">
                        <el-input
                            v-model.trim="data.ruleForm.num"
                            :prefix-icon="Lock"
                            style="width: 150px;"
                            placeholder="输入验证码"
                            size="large"
                            clearable
                        >
                        </el-input>
                        <div v-loading="codeLoading" style="height: 38px; width: 120px;">
                          <el-tooltip
                              effect="dark"
                              content="点击更换验证码"
                              placement="right"
                          >
                            <img @click="getCode" style="height: 38px; width: 120px;cursor: pointer;" :src="codeImg" alt="验证码" v-if="codeImg">
                          </el-tooltip>
                        </div>


                      </div>
                    </el-form-item>

                    <el-form-item class="form-btn">
                        <el-button color="#0099cc" size="large" :loading="btn_loading" @click="submitForm(ruleFormRef)"> 登录</el-button>
                    </el-form-item>
                </el-form>
            </div>
            <p class="copyright">
                <el-link href="http://www.huashuyn.com/" :underline="false" target="_blank">©技术支持：蚂蚁雄兵</el-link>
            </p>
        </div>

        <vue-particles id="tsparticles" :particlesInit="particlesInit" :particlesLoaded="particlesLoaded" :options="data.options" />

        <!-- 滑块+拼图验证 -->
        <el-dialog
            v-model="dialogSlider"
            class="dialog-sku"
            title="拼图验证"
            width="300px"
            top="30vh"
            :close-on-click-modal="false"
            :append-to-body="true"
            :destroy-on-close="true"
            @close="dialogSlider = false"
        >
            <slide-verify
                ref="sliderImg"
                :slider-text="sliderText"
                :accuracy="5"
                :show="false"
                :imgs="imgArr"
                :w="260"
                :h="220"
                @again="onAgain"
                @success="onSuccess"
                @fail="onFail"
            ></slide-verify>
        </el-dialog>
    </div>
</template>

<script setup>
import { getCurrentInstance, ref, reactive, onMounted, onBeforeUnmount } from "vue"
import { useRouter } from "vue-router"
import addDynamicRoute from "@/router/addDynamicRoute";

import { useBaseStore } from "@store/base"
import { Lock, User } from "@element-plus/icons-vue"
import { ElNotification } from "element-plus"
import { loadFull } from "tsparticles"
import logo from "@assets/logo.png"
import img1 from "@images/img1.jpg"
import img2 from "@images/img2.jpg"
import img3 from "@images/img3.jpg"
import img4 from "@images/img4.jpg"
import img5 from "@images/img5.jpg"
import SlideVerify from "vue3-slide-verify"
import "vue3-slide-verify/dist/style.css"
import JSEncrypt from "jsencrypt"

const router = useRouter()
const storeBase = useBaseStore() // 基础信息
const { proxy } = getCurrentInstance()

onMounted(() => {
    getCode();
    getKey();
})
onBeforeUnmount(() => {
    sliderImg.value = null
    ruleFormRef.value = null
    imgArr.value = []
    data.options = null
})

const data = reactive({
    options: {
        fpsLimit: 100,
        interactivity: {
            events: {
                onClick: {
                    enable: true,
                    mode: "push",
                },
                onHover: {
                    enable: true,
                    mode: "grab",
                },
                resize: true,
            },
            modes: {
                bubble: {
                    distance: 400,
                    duration: 2,
                    opacity: 0.6,
                    size: 10,
                },
                push: {
                    quantity: 4,
                },
                repulse: {
                    distance: 200,
                    duration: 0.4,
                },
            },
        },
        particles: {
            color: {
                value: "#ffffff",
            },
            links: {
                color: "#ffffff",
                distance: 150,
                enable: true,
                opacity: 0.5,
                width: 1,
            },
            collisions: {
                enable: true,
            },
            move: {
                direction: "none",
                enable: true,
                outMode: "bounce",
                random: false,
                speed: 2,
                straight: false,
            },
            number: {
                density: {
                    enable: true,
                    value_area: 800,
                },
                value: 60,
            },
            opacity: {
                value: 0.5,
            },
            shape: {
                type: "circle",
            },
            size: {
                random: true,
                value: 3,
            },
        },
        detectRetina: true,
    },
    ruleForm: {
      userName: "admin",
      password: "123456",
      num:""
    },
    rules: {
      // userName: [{ validator: proxy.$util.validPhone, trigger: "blur" }],
      userName: [{ required: true, message: "请输入账号", trigger: "blur" }],
      password: [{ required: true, message: "请输入密码", trigger: "blur" }],
      num: [{ required: true, message: "请输入验证码", trigger: "blur" }],
    },
})

// 粒子效果-基于 npm i vue3-particles
const particlesInit = async (engine) => {
    await loadFull(engine)
}
const particlesLoaded = async (container) => {
    // console.log("Particles container loaded", container)
}

const ruleFormRef = ref(null)
const btn_loading = ref(false)

/**
 * 滑块+拼图验证 vue3-slide-verify
 * @property {Number} w canvas width
 * @property {Number} h canvas height
 * @property {Number} accuracy 滑动验证的误差范围，默认值 5
 * @property {Array} imgArr picture array 背景图数组，默认值 []
 * @property {String} sliderText 滑块中提示文字
 * @property {Function} onAgain 检测到非人为操作滑动时触发的回调函数
 * @property {Function} onSuccess 成功回调
 * @property {Function} onFail 失败处理
 * @property {Function} onRefresh 点击刷新按钮后
 */
const isSliderVerify = ref(false); //登录时是否开启滑块+拼图验证
const sliderText = ref("向右滑动 >>")
const imgArr = [img1, img2, img3, img4, img5]
const sliderImg = ref(null)
const dialogSlider = ref(false)
const onAgain = () => {
    proxy.$message({ message: "检测到非人为操作！ try again", type: "error" })
    sliderImg.value.refresh() // 刷新
}
const onSuccess = (times) => {
    logins()
}
const onFail = () => {
    proxy.$message({ message: "验证不通过", type: "error" })
}

const submitForm = (formEl) => {
    if (!formEl) return
    formEl.validate((valid, fields) => {
        if (valid) {
            if(isSliderVerify.value){
              dialogSlider.value = true
            }else{
              logins()
            }
        }
    })
}

function logins() {
    if(isSliderVerify.value){
      sliderImg.value.refresh() // 刷新
      dialogSlider.value = false
    }
    btn_loading.value = true
    let encryptor = new JSEncrypt() // 创建加密对象实例
    encryptor.setPublicKey(pub_keys.value) // 设置公钥
    let pass = encryptor.encrypt(data.ruleForm.password) // 对内容进行加密
    proxy.$axios
        .post("/authentication/login/pc", {
            userName: data.ruleForm.userName,
            password: pass,
        },{
          headers: {
            "CAP_UID": codeUuid.value,
            "CAP_VAL": data.ruleForm.num
          }
        })
        .then((res) => {
            btn_loading.value = false
            if(res.data.code === 200){
              let result = res.data.data
              localStorage.setItem("token", result.accessToken)

              if (result.admin) {
                storeBase.setPermissions(["*:*:*"])
              } else {
                storeBase.setPermissions(result.permissionSet)
              }
              storeBase.setMenuTree(result.menuTree)
              addDynamicRoute(result.menuTree)
              // localStorage.setItem("bosid", result.tenant_id)
              // proxy.$util.hidePhone(result.mobile) 隐藏手机号中间
              let infos = {
                // mobile: result.mobile,
                // master_id: result.master_id,
                // tenant_id: result.tenant_id,
                admin_id: result.uid,
                ...result
              }
              delete infos.menuTree
              delete infos.permissionSet

              storeBase.setInfo(infos)
              storeBase.setCur(0)
              // storeBase.setUserAuth(0) // 用户端小程序是否授权，0是未授权，1已授权
              // storeBase.setStaffAuth(0) // 员工端小程序是否授权，0是未授权，1已授权
              // storeBase.setSupplierAuth(0) // 供应商端小程序是否授权，0是未授权，1已授权
              storeBase.setStyle(true)
              router.replace("/Home")
              ElNotification({
                title: "登录成功",
                message: "欢迎回来",
                type: "success",
                duration: 3000,
              })
            }else{
              proxy.$message({ message: res.data.msg, type: "error" })
            }
        })
        .catch((err) => {
            btn_loading.value = false;
        })
}

const pub_keys = ref("")
function getKey() {
  // pub_keys.value = '-----BEGIN PUBLIC KEY-----\n' +
  // 'MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAv7bkFih6Ll92n2YBKk2g\n' +
  // 'y2jDtbCrJEJPwE9UdtaPTavrqGUqbYKdxRuVxWyltJttTog4sdnEY6NQ8dAjP5uY\n' +
  // 'jIugU+oRtW5iGIrbFLZd4IK+c8tnX3Vx4NlxTXxqabBSwcVIJ8w5rL4uGFyTloKo\n' +
  // 'Pnx8LKSyYxYEHAF6qEpNdR/16NzYhKJALziLJ5ZH4J3DsFtcmoQMBew/6DEelcl1\n' +
  // 'ygqjh79Kd5Wu502cQWh34Pc7cHB7M110cpuJXjbQ220djbtY0d5yQy7KT39TuhOZ\n' +
  // 'iR1MqZfPU8pKTD5emfOHzP4vNkS3034kAlRasKRI/jHp5KCJmE7oaGfkPa1msYL2\n' +
  // 'CwIDAQAB\n' +
  // '-----END PUBLIC KEY-----'
    proxy.$axios
        .get("authentication/public-key")
        .then((res) => {
          // console.log(res);
            if (res.data.code === 200) {
                pub_keys.value = res.data.data
            } else {
                proxy.$message({ message: res.data.msg, type: "error" })
            }
        })
        .catch((err) => {})
}

// 验证码
const codeLoading = ref(false);
const codeUuid = ref(null)
const codeImg = ref(null)
function getCode() {
  codeLoading.value = true;
  proxy.$axios
      .get("/captcha")
      .then((res) => {
        if (res.data.code == 200) {
          codeUuid.value = res.data.data.uuid
          codeImg.value = res.data.data.img
        } else {
            try {
              proxy.$message({ message: res.data.msg, type: "error" })
            }catch (e) {
              proxy.$message({ message: '服务错误', type: "error" })
            }
        }
      })
      .catch((err) => { })
      .finally(()=>{
        codeLoading.value = false;
      })
}

</script>
<script>
export default {
    name: "Login",
}
</script>

<style lang="less" scoped>
.copyright {
    width: 100%;
    text-align: center;

    .el-link.el-link--default {
        color: #999;

        &:hover {
            color: #0099cc;
        }
    }
}

.login-box {
    z-index: 10;
    width: 400px;
    border-radius: 5px;
    padding-bottom: 50px;
    background: white;
    box-shadow: 0px 0px 5px #333333;

    .login-top {
        width: 100%;
        text-align: center;
        margin-bottom: 50px;
        padding-top: 50px;

        .el-image {
            width: 220px; // 用公司logo样式
            // width:100px; // 花logo
        }
    }

    .login-center {
        padding: 0 60px;
    }

    :deep(.el-form-item__label) {
        &::before {
            content: "" !important;
        }
    }

    .form-btn {
        margin: 44px 0px 20px;

        :deep(.el-form-item__content) {
            margin: 0 !important;

            .el-button {
                width: 100%;
                letter-spacing: 1px;
            }
        }
    }
}

.login-bg {
    width: 100%;
    height: 100%;
    // background: url("../assets/images/bg.jpg") no-repeat center;
    background: url("https://cdn.huashushop.com/tenant_593be52a46f869eea8b31d146d21de7a/album/202304/20230413_e075ad13466618560820ebf0691e9cb9.jpg") no-repeat
        center;
    background-size: cover;
    display: flex;
    align-items: center;
    justify-content: center;
    flex-direction: column;
    overflow: hidden;
    position: relative;
}
</style>
<style lang="less">
.dialog-sku {
    .el-dialog__body {
        padding: 10px 20px 20px;
    }
}
</style>

